package pl.mmadej.ds4java.ds.list;


import pl.mmadej.ds4java.ds.common.DataStructure;

import java.util.Iterator;

abstract class AbstractList<T> extends DataStructure<T> implements List<T> {

    private int size;

    @Override
    public int size() {
        return size;
    }

    @Override
    public boolean empty() {
        return size == 0;
    }

    @Override
    public int hashCode() {
        int hashCode = 1;
        Iterator<T> iterator = iterator();
        while (iterator.hasNext()) {
            hashCode = 29 * hashCode + iterator.next().hashCode();
        }
        return hashCode;
    }

    @Override
    @SuppressWarnings("unchecked")
    public boolean equals(Object obj) {
        if (!(obj instanceof List)) {
            return false;
        }
        List<T> list = (List<T>) obj;
        if (list.size() != size()) {
            return false;
        }
        Iterator<T> iterator1 = iterator();
        Iterator<T> iterator2 = list.iterator();
        while (iterator1.hasNext()) {
            if (!iterator1.next().equals(iterator2.next())) {
                return false;
            }
        }
        return true;
    }

    public String toString() {
        if (empty()) {
            return "[]";
        }
        StringBuilder sb = new StringBuilder().append('[');
        Iterator<T> iterator = iterator();
        for (; ; ) {
            T e = iterator.next();
            sb.append(e == this ? "(this Collection)" : e);
            if (!iterator.hasNext())
                return sb.append(']').toString();
            sb.append(", ");
        }
    }

    protected void setSize(int newSize) {
        size = newSize;
    }

    protected int incrementSize() {
        return size++;
    }

    protected void decrementSize() {
        size--;
    }

}
